package com.asa.tongji.huiguifenxi;

import com.asa.hutils.MathHUtils;
import com.asa.tongji.FenBuFunction;
import com.asa.tongji.TUtils1;
import com.asa.tongji.TUtils2;
import com.asa.tongji.bean.ChongHuiGuiFenXiBaoGao;

public class ChongHuiGui {
	
	
	
	
	
	public static void main(String[] args) throws Exception {
		double[] x1 = new double[10];
		double[] x2 = new double[10];
		double[] y = new double[10];
		
		
		x1[0] = 10;
		x1[1] = 8;
		x1[2] = 8;
		x1[3] = 5;
		x1[4] = 7;
		x1[5] = 8;
		x1[6] = 7;
		x1[7] = 9;
		x1[8] = 6;
		x1[9] = 9;
		
		x2[0] = 80;
		x2[1] = 0;
		x2[2] = 200;
		x2[3] = 200;
		x2[4] = 300;
		x2[5] = 230;
		x2[6] = 40;
		x2[7] = 0;
		x2[8] = 330;
		x2[9] = 180;
		
		y[0] = 469;
		y[1] = 366;
		y[2] = 371;
		y[3] = 208;
		y[4] = 246;
		y[5] = 297;
		y[6] = 363;
		y[7] = 436;
		y[8] = 198;
		y[9] = 364;
		
		double[][] x = new double[2][];
		x[0] = x1;
		x[1] = x2;
		
		
		chonghuiguifenxi(y,x);
			
		
	}


	public static ChongHuiGuiFenXiBaoGao chonghuiguifenxi(double[] y,double[][] x) throws Exception {
//		double correlationCoefficient1 = TUtils1.correlationCoefficient(x1, y);
//		double correlationCoefficient2 = TUtils1.correlationCoefficient(x2, y);
//		//System.out.println(correlationCoefficient1+":"+correlationCoefficient2);
		
		double[] E = new double[y.length];
		for (int i = 0; i < E.length; i++) {
			E[i] = 1;
		}
		
		
		double[][] a = new double[x.length+1][x[0].length];
		
		for (int i = 0; i < x.length; i++) {
			a[i] = x[i];
		}
		a[a.length-1] = E;
		
		for (int i = 0; i < a.length; i++) {
			for (int j = 0; j < a[i].length; j++) {
				System.out.print(a[i][j]+"  ");
			}
			//System.out.println();
		}
		
		double[][] b = MathHUtils.zhuanzhi(a);
		for (int i = 0; i < b.length; i++) {
			for (int j = 0; j < b[i].length; j++) {
				System.out.print(b[i][j]+"  ");
			}
			//System.out.println();
		}
		//System.out.println("**************************chenfa******************************");
		double[][] chenfa = MathHUtils.chenfa(a, b);
		for (int i = 0; i < chenfa.length; i++) {
			for (int j = 0; j < chenfa[i].length; j++) {
				System.out.print(chenfa[i][j]+"  ");
			}
			//System.out.println();
		}
		double[][] juzhengni = MathHUtils.juzhengni(chenfa);
//		juzhengni[2][2] = 5.2114;
		//System.out.println("=========================juzhengni==========================");
		for (int i = 0; i < juzhengni.length; i++) {
			for (int j = 0; j < juzhengni[i].length; j++) {
				System.out.print(juzhengni[i][j]+"  ");
			}
			//System.out.println();
		}
		double[][] chenfa2 = MathHUtils.chenfa(juzhengni, a);
		//System.out.println("=========================chenfa2==========================");
		for (int i = 0; i < chenfa2.length; i++) {
			for (int j = 0; j < chenfa2[i].length; j++) {
				System.out.print(chenfa2[i][j]+"  ");
			}
			//System.out.println();
		}
		double[][] bb = new double[1][];
		bb[0] = y;
		double[][] chenfa3 = MathHUtils.chenfa(chenfa2,MathHUtils.zhuanzhi(bb));
		//System.out.println("=========================chenfa3==========================");
		for (int i = 0; i < chenfa3.length; i++) {
			for (int j = 0; j < chenfa3[i].length; j++) {
				System.out.print(chenfa3[i][j]+"  ");
			}
			//System.out.println("chenfa3");
		}
		
		System.out.print("y=");
		for (int i = 0; i < chenfa3.length-1; i++) {
			if (chenfa3[i][0]>0&&i!=0) {
				System.out.print("+"+chenfa3[i][0]+"x");
			}else{
				System.out.print(chenfa3[i][0]+"x");
			}
		}
		
		if (chenfa3[chenfa3.length-1][0]>0) {
			//System.out.println("+"+chenfa3[chenfa3.length-1][0]);
		}else{
			//System.out.println(chenfa3[chenfa3.length-1][0]);
		}
		
		
		
		/**
		 * 确认精度
		 */
		//System.out.println("y_[i]y_[i]y_[i]y_[i]y_[i]y_[i]y_[i]y_[i]");
		double[] y_ = new double[y.length];//预测值
		for (int i = 0; i < y_.length; i++) {
			
			for (int j = 0; j < x.length; j++) {
		
				y_[i] += x[j][i]*chenfa3[j][0];
				
//				y_[i] += x1[i]*chenfa3[0][0]+x2[i]*chenfa3[1][0]+chenfa3[2][0];
			}
			y_[i] += chenfa3[chenfa3.length-1][0];
			
			//System.out.println(y_[i]);
			
		}
		//System.out.println("y_[i]y_[i]y_[i]y_[i]y_[i]y_[i]y_[i]y_[i]");
		double syy = TUtils1.variance(y)*y.length;
		//System.out.println(syy+"syysyysyysyysyy");
		
		double sy_y_ = TUtils1.variance(y_)*y_.length;
		//System.out.println(sy_y_+"sy_y_sy_y_sy_y_sy_y_sy_y_sy_y_");
		
		double syy_ = TUtils1.covariance(y, y_) * y.length;
		//System.out.println(syy_+"syy_syy_syy_syy_syy_syy_syy_syy_syy_syy_");
		
		double se = 0;
		
		for (int i = 0; i < y_.length; i++) {
			se += (y[i]-y_[i])*(y[i]-y_[i]);
		}
		
		//System.out.println(se+"sesesesesese");
		
		double r = syy_/Math.sqrt(syy*sy_y_);//重相关系数
		//System.out.println(r+"rrrrrrrrrrrrrrrrrrrrrrrrrrrrrrrrrrrr"+syy_+"  "+Math.sqrt(syy*sy_y_));
		double rr  = r*r;//判定系数
		//System.out.println(rr);
		
		
		
		/**
		 * 修正自由度的判定系数
		 * 
		 * R^ = 1-(se/(样本个数-自变量个数-1))/(syy/(样本个数-1))
		 * 
		 */
		
		double rr2 = 1-(se/(y.length-2-1))/(syy/(y.length-1));
		//System.out.println(rr2);
		
		
		
		/**
		 * 回归系数的检验
		 * f检验的函数拟合性有问题，先用t检验吧，效果是一样的
		 */
		double o = Math.sqrt(se/(y.length-2-1));//统计学中A1、A2、B对应，o是方差
		;
		double t = FenBuFunction.tfengbu(0.95, y.length - 2);
		
		//System.out.println(o+"       "+t);
		if (o>t) {
			//System.out.println("置信度95%，可信");
		}else{
			//System.out.println("置信度95%，不可信");
		}
		
		//置信区间
		double[] canshu = new double[chenfa3.length];
		for (int i = 0; i < canshu.length; i++) {
			canshu[i] = chenfa3[i][0];
		}
		double oo = TUtils1.standardDeviation(y);
		double[][] xtoy = xtoy(x, canshu , oo , y.length);
		
		
		//标准化残差
		
		
		
		//System.out.println(x.length);
		//System.out.println(x[0].length);
		double[] biaozhuncancha = biaozhuncancha(chenfa3, se, x, y);
		//System.out.println("标准化残差");
		for (int i = 0; i < biaozhuncancha.length; i++) {
			//System.out.println(biaozhuncancha[i]);
		}
		
		
		ChongHuiGuiFenXiBaoGao baoGao = new ChongHuiGuiFenXiBaoGao();
		baoGao.setC(chenfa3);
		baoGao.setRr(rr);
		baoGao.setZhixindu(0.95);
		baoGao.setDuiyujieguozhixindujianyantongguo(o>t);
		baoGao.setOo(oo);
		
		
		return baoGao;
	}
	
	
	/**
	 * one x to y[,] 求特定的置信区间
	 * 
	 * @param x
	 *            自变量
	 * @param a
	 *            回归函数斜率
	 * @param b
	 *            回归函数b
	 * @param oo
	 *            总体样本的标准差
	 * @param n
	 *            样本数量
	 * @return
	 */
	public static double[][] xtoy(double x[][], double[] a, double oo, int n) {
		// 具体某一x确定，y的置信区间
		double[][] yy = new double[x[0].length][2];
		for (int i = 0; i < x[0].length; i++) {
			double uy = 0;
			for (int j = 0; j < x.length; j++) {
				uy += x[j][i]*a[j];
			}
			uy += a[a.length-1];
			yy[i] = TUtils2.zongtijunzhi(n, oo, uy, 0.9);// 置信区间，没有用f的使用正态的
		}

		return yy;
	}
	
	// 具体某一x确定，y的置信区间
	public static double[] xtoy(double x[], double[] a, double oo, int n,double aa) {
		
			double[] yy = new double[2];

			double uy = 0;
			for (int j = 0; j < a.length-1; j++) {
				uy += x[j]*a[j];
			}
			uy += a[a.length-1];
			yy = TUtils2.zongtijunzhi(n, oo, uy, aa);// 置信区间，没有用f的使用正态的

		return yy;
	}
	
	
	/**
	 * 标准化残差
	 */
	public static double[] biaozhuncancha(double[][] a, double se, double[][] x, double[] y) {
		double[] y__ = new double[y.length];
		double[] y_ = new double[y.length];
		
		for (int i = 0; i < x[0].length; i++) {
			for (int j = 0; j < x.length; j++) {
				y_[i]+=x[j][i]*a[j][0];
			}
		}
		
		for (int i = 0; i < y_.length; i++) {
			y_[i] += a[a.length-1][0];
		}
		
		for (int i = 0; i < y.length; i++) {
			y__[i] = (y[i] - y_[i]) / (Math.sqrt(se / (y.length - x.length -1)));
			//System.out.println(y[i]);
		}
		return y__;
	}
	
	


}
